From 061160d30e36649a72eda2d6d1052ac2d320bacb Mon Sep 17 00:00:00 2001 From: "gm281@boulderdash.cl.cam.ac.uk" Date: Tue, 3 Aug 2004 16:01:12 +0000 Subject: [PATCH] bitkeeper revision 1.1133 (410fb6c8BCfflcDT6Pjhr8MK2MOc2A) The initial implementation of the warping in BVT --- tools/libxc/xc.h | 18 ++-- tools/libxc/xc_bvtsched.c | 36 ++++--- tools/python/xen/lowlevel/xc/xc.c | 53 +++++---- tools/python/xen/xend/XendClient.py | 13 +-- tools/python/xen/xend/XendDomain.py | 5 +- tools/python/xen/xend/server/SrvDomain.py | 3 +- tools/python/xen/xm/main.py | 6 +- xen/common/sched_bvt.c | 125 ++++++++++++++++------ xen/include/hypervisor-ifs/sched_ctl.h | 9 +- 9 files changed, 175 insertions(+), 93 deletions(-) diff --git a/tools/libxc/xc.h b/tools/libxc/xc.h index d95a735372..8b7ee33273 100644 --- a/tools/libxc/xc.h +++ b/tools/libxc/xc.h @@ -98,20 +98,22 @@ int xc_bvtsched_global_set(int xc_handle, int xc_bvtsched_domain_set(int xc_handle, u32 domid, - unsigned long mcuadv, - unsigned long warp, - unsigned long warpl, - unsigned long warpu); + u32 mcuadv, + int warpback, + s32 warpvalue, + long long warpl, + long long warpu); int xc_bvtsched_global_get(int xc_handle, unsigned long *ctx_allow); int xc_bvtsched_domain_get(int xc_handle, u32 domid, - unsigned long *mcuadv, - unsigned long *warp, - unsigned long *warpl, - unsigned long *warpu); + u32 *mcuadv, + int *warpback, + s32 *warpvalue, + long long *warpl, + long long *warpu); int xc_fbvtsched_global_set(int xc_handle, unsigned long ctx_allow); diff --git a/tools/libxc/xc_bvtsched.c b/tools/libxc/xc_bvtsched.c index aeaddcfb04..783ab30318 100644 --- a/tools/libxc/xc_bvtsched.c +++ b/tools/libxc/xc_bvtsched.c @@ -40,10 +40,11 @@ int xc_bvtsched_global_get(int xc_handle, int xc_bvtsched_domain_set(int xc_handle, u32 domid, - unsigned long mcuadv, - unsigned long warp, - unsigned long warpl, - unsigned long warpu) + u32 mcuadv, + int warpback, + s32 warpvalue, + long long warpl, + long long warpu) { dom0_op_t op; struct bvt_adjdom *bvtadj = &op.u.adjustdom.u.bvt; @@ -53,20 +54,22 @@ int xc_bvtsched_domain_set(int xc_handle, op.u.adjustdom.sched_id = SCHED_BVT; op.u.adjustdom.direction = SCHED_INFO_PUT; - bvtadj->mcu_adv = mcuadv; - bvtadj->warp = warp; - bvtadj->warpl = warpl; - bvtadj->warpu = warpu; + bvtadj->mcu_adv = mcuadv; + bvtadj->warpback = warpback; + bvtadj->warpvalue = warpvalue; + bvtadj->warpl = warpl; + bvtadj->warpu = warpu; return do_dom0_op(xc_handle, &op); } int xc_bvtsched_domain_get(int xc_handle, u32 domid, - unsigned long *mcuadv, - unsigned long *warp, - unsigned long *warpl, - unsigned long *warpu) + u32 *mcuadv, + int *warpback, + s32 *warpvalue, + long long *warpl, + long long *warpu) { dom0_op_t op; @@ -80,9 +83,10 @@ int xc_bvtsched_domain_get(int xc_handle, ret = do_dom0_op(xc_handle, &op); - *mcuadv = adjptr->mcu_adv; - *warp = adjptr->warp; - *warpl = adjptr->warpl; - *warpu = adjptr->warpu; + *mcuadv = adjptr->mcu_adv; + *warpback = adjptr->warpback; + *warpvalue = adjptr->warpvalue; + *warpl = adjptr->warpl; + *warpu = adjptr->warpu; return ret; } diff --git a/tools/python/xen/lowlevel/xc/xc.c b/tools/python/xen/lowlevel/xc/xc.c index 21d40b026e..fc5bafd81b 100644 --- a/tools/python/xen/lowlevel/xc/xc.c +++ b/tools/python/xen/lowlevel/xc/xc.c @@ -435,18 +435,23 @@ static PyObject *pyxc_bvtsched_domain_set(PyObject *self, { XcObject *xc = (XcObject *)self; - u32 dom; - unsigned long mcuadv, warp, warpl, warpu; - - static char *kwd_list[] = { "dom", "mcuadv", "warp", "warpl", - "warpu", NULL }; - - if ( !PyArg_ParseTupleAndKeywords(args, kwds, "illll", kwd_list, - &dom, &mcuadv, &warp, &warpl, &warpu) ) + u32 dom; + u32 mcuadv; + int warpback; + s32 warpvalue; + long long warpl; + long long warpu; + + static char *kwd_list[] = { "dom", "mcuadv", "warpback", "warpvalue", + "warpl", "warpu", NULL }; + + if ( !PyArg_ParseTupleAndKeywords(args, kwds, "iiiill", kwd_list, + &dom, &mcuadv, &warpback, &warpvalue, + &warpl, &warpu) ) return NULL; if ( xc_bvtsched_domain_set(xc->xc_handle, dom, mcuadv, - warp, warpl, warpu) != 0 ) + warpback, warpvalue, warpl, warpu) != 0 ) return PyErr_SetFromErrno(xc_error); Py_INCREF(zero); @@ -459,23 +464,28 @@ static PyObject *pyxc_bvtsched_domain_get(PyObject *self, { XcObject *xc = (XcObject *)self; u32 dom; - unsigned long mcuadv, warp, warpl, warpu; + u32 mcuadv; + int warpback; + s32 warpvalue; + long long warpl; + long long warpu; static char *kwd_list[] = { "dom", NULL }; if ( !PyArg_ParseTupleAndKeywords(args, kwds, "i", kwd_list, &dom) ) return NULL; - if ( xc_bvtsched_domain_get(xc->xc_handle, dom, &mcuadv, &warp, - &warpl, &warpu) != 0 ) + if ( xc_bvtsched_domain_get(xc->xc_handle, dom, &mcuadv, &warpback, + &warpvalue, &warpl, &warpu) != 0 ) return PyErr_SetFromErrno(xc_error); return Py_BuildValue("{s:i,s:l,s:l,s:l,s:l}", "domain", dom, "mcuadv", mcuadv, - "warp", warp, - "warpl", warpl, - "warpu", warpu); + "warpback", warpback, + "warpvalue", warpvalue, + "warpl", warpl, + "warpu", warpu); } static PyObject *pyxc_fbvtsched_global_set(PyObject *self, @@ -1040,12 +1050,13 @@ static PyMethodDef pyxc_methods[] = { (PyCFunction)pyxc_bvtsched_domain_set, METH_VARARGS | METH_KEYWORDS, "\n" "Set per-domain tuning parameters for Borrowed Virtual Time scheduler.\n" - " dom [int]: Identifier of domain to be tuned.\n" - " mcuadv [int]: Proportional to the inverse of the domain's weight.\n" - " warp [int]: How far to warp domain's EVT on unblock.\n" - " warpl [int]: How long the domain can run warped.\n" - " warpu [int]: How long before the domain can warp again.\n\n" - "Returns: [int] 0 on success; -1 on error.\n" }, + " dom [int]: Identifier of domain to be tuned.\n" + " mcuadv [int]: Proportional to the inverse of the domain's weight.\n" + " warpback [int]: Warp ? \n" + " warpvalue [int]: How far to warp domain's EVT on unblock.\n" + " warpl [int]: How long the domain can run warped.\n" + " warpu [int]: How long before the domain can warp again.\n\n" + "Returns: [int] 0 on success; -1 on error.\n" }, { "bvtsched_domain_get", (PyCFunction)pyxc_bvtsched_domain_get, diff --git a/tools/python/xen/xend/XendClient.py b/tools/python/xen/xend/XendClient.py index cc5b06fd10..09ea1cc2ea 100644 --- a/tools/python/xen/xend/XendClient.py +++ b/tools/python/xen/xend/XendClient.py @@ -490,13 +490,14 @@ class Xend: {'op' : 'pincpu', 'cpu' : cpu }) - def xend_domain_cpu_bvt_set(self, id, mcuadv, warp, warpl, warpu): + def xend_domain_cpu_bvt_set(self, id, mcuadv, warpback, warpvalue, warpl, warpu): return self.xendPost(self.domainurl(id), - {'op' : 'cpu_bvt_set', - 'mcuadv' : mcuadv, - 'warp' : warp, - 'warpl' : warpl, - 'warpu' : warpu }) + {'op' : 'cpu_bvt_set', + 'mcuadv' : mcuadv, + 'warpback' : warpback, + 'warpvalue': warpvalue, + 'warpl' : warpl, + 'warpu' : warpu }) def xend_domain_cpu_fbvt_set(self, id, mcuadv, warp, warpl, warpu): return self.xendPost(self.domainurl(id), diff --git a/tools/python/xen/xend/XendDomain.py b/tools/python/xen/xend/XendDomain.py index ce00717eb7..fbb6275b7a 100644 --- a/tools/python/xen/xend/XendDomain.py +++ b/tools/python/xen/xend/XendDomain.py @@ -592,13 +592,14 @@ class XendDomain: except Exception, ex: raise XendError(str(ex)) - def domain_cpu_bvt_set(self, id, mcuadv, warp, warpl, warpu): + def domain_cpu_bvt_set(self, id, mcuadv, warpback, warpvalue, warpl, warpu): """Set BVT (Borrowed Virtual Time) scheduler parameters for a domain. """ dominfo = self.domain_lookup(id) try: return xc.bvtsched_domain_set(dom=dominfo.dom, mcuadv=mcuadv, - warp=warp, warpl=warpl, warpu=warpu) + warpback=warpback, warpvalue=warpvalue, + warpl=warpl, warpu=warpu) except Exception, ex: raise XendError(str(ex)) diff --git a/tools/python/xen/xend/server/SrvDomain.py b/tools/python/xen/xend/server/SrvDomain.py index 7b398a3606..983b7e4320 100644 --- a/tools/python/xen/xend/server/SrvDomain.py +++ b/tools/python/xen/xend/server/SrvDomain.py @@ -110,7 +110,8 @@ class SrvDomain(SrvDir): fn = FormFn(self.xd.domain_cpu_bvt_set, [['dom', 'str'], ['mcuadv', 'int'], - ['warp', 'int'], + ['warpback', 'int'], + ['warpvalue', 'int'], ['warpl', 'int'], ['warpu', 'int']]) val = fn(req.args, {'dom': self.dom.name}) diff --git a/tools/python/xen/xm/main.py b/tools/python/xen/xm/main.py index e1ff33ed87..f331db9cd3 100644 --- a/tools/python/xen/xm/main.py +++ b/tools/python/xen/xm/main.py @@ -492,12 +492,12 @@ class ProgBvt(Prog): info = """Set BVT scheduler parameters.""" def help(self, args): - print args[0], "DOM MCUADV WARP WARPL WARPU" + print args[0], "DOM MCUADV WARPBACK WARPVALUE WARPL WARPU" print '\nSet Borrowed Virtual Time scheduler parameters.' def main(self, args): - if len(args) != 6: self.err("%s: Invalid argument(s)" % args[0]) - v = map(int, args[1:6]) + if len(args) != 7: self.err("%s: Invalid argument(s)" % args[0]) + v = map(int, args[1:7]) server.xend_domain_cpu_bvt_set(*v) xm.prog(ProgBvt) diff --git a/xen/common/sched_bvt.c b/xen/common/sched_bvt.c index 087f7ccc6e..2cb2f3793f 100644 --- a/xen/common/sched_bvt.c +++ b/xen/common/sched_bvt.c @@ -32,15 +32,17 @@ struct bvt_dom_info { struct domain *domain; /* domain this info belongs to */ struct list_head run_list; /* runqueue list pointers */ - unsigned long mcu_advance; /* inverse of weight */ + u32 mcu_advance; /* inverse of weight */ u32 avt; /* actual virtual time */ u32 evt; /* effective virtual time */ int warpback; /* warp? */ - long warp; /* virtual time warp */ - long warpl; /* warp limit */ - long warpu; /* unwarp time requirement */ - s_time_t warped; /* time it ran warped last time */ - s_time_t uwarped; /* time it ran unwarped last time */ + int warp; /* warp set and within the warp + limits*/ + s32 warp_value; /* virtual time warp */ + s_time_t warpl; /* warp limit */ + struct ac_timer warp_timer; /* deals with warpl */ + s_time_t warpu; /* unwarp time requirement */ + struct ac_timer unwarp_timer; /* deals with warpu */ }; struct bvt_cpu_info @@ -91,6 +93,43 @@ static inline int __task_on_runqueue(struct domain *d) return (RUNLIST(d))->next != NULL; } + +/* Warp/unwarp timer functions */ +static void warp_timer_fn(unsigned long pointer) +{ + struct bvt_dom_info *inf = (struct bvt_dom_info *)pointer; + +printk("--> Warp timer fired for %d\n", inf->domain->domain); + inf->warp = 0; + /* unwarp equal to zero => stop warping */ + if(inf->warpu == 0) + { + inf->warpback = 0; + goto reschedule; + } + + /* set unwarp timer */ + inf->unwarp_timer.expires = NOW() + inf->warpu; + add_ac_timer(&inf->unwarp_timer); + +reschedule: + cpu_raise_softirq(inf->domain->processor, SCHEDULE_SOFTIRQ); +} + +static void unwarp_timer_fn(unsigned long pointer) +{ + struct bvt_dom_info *inf = (struct bvt_dom_info *)pointer; + +printk("---> UnWarp timer fired for %d\n", inf->domain->domain); + if(inf->warpback) + { + inf->warp = 1; + cpu_raise_softirq(inf->domain->processor, SCHEDULE_SOFTIRQ); + } +} + + + static inline u32 calc_avt(struct domain *d, s_time_t now) { u32 ranfor, mcus; @@ -112,8 +151,8 @@ static inline u32 calc_evt(struct domain *d, u32 avt) struct bvt_dom_info *inf = BVT_INFO(d); /* TODO The warp routines need to be rewritten GM */ - if ( inf->warpback ) - return avt - inf->warp; + if ( inf->warp ) + return avt - inf->warp_value; else return avt; } @@ -144,6 +183,21 @@ void bvt_add_task(struct domain *p) inf->mcu_advance = MCU_ADVANCE; inf->domain = p; + inf->warpback = 0; + /* Set some default values here. */ + inf->warp = 0; + inf->warp_value = 0; + inf->warpl = MILLISECS(2000); + inf->warpu = MILLISECS(1000); + /* initialise the timers */ + init_ac_timer(&inf->warp_timer); + inf->warp_timer.cpu = p->processor; + inf->warp_timer.data = (unsigned long)inf; + inf->warp_timer.function = &warp_timer_fn; + init_ac_timer(&inf->unwarp_timer); + inf->unwarp_timer.cpu = p->processor; + inf->unwarp_timer.data = (unsigned long)inf; + inf->unwarp_timer.function = &unwarp_timer_fn; if ( p->domain == IDLE_DOMAIN_ID ) { @@ -154,12 +208,7 @@ void bvt_add_task(struct domain *p) /* Set avt and evt to system virtual time. */ inf->avt = CPU_SVT(p->processor); inf->evt = CPU_SVT(p->processor); - /* Set some default values here. */ - inf->warpback = 0; - inf->warp = 0; - inf->warpl = 0; - inf->warpu = 0; - } + } return; } @@ -274,7 +323,7 @@ void bvt_free_task(struct domain *p) */ static void bvt_do_block(struct domain *p) { - BVT_INFO(p)->warpback = 0; + // TODO what when blocks? BVT_INFO(p)->warpback = 0; } /* Control the scheduler. */ @@ -303,16 +352,17 @@ int bvt_adjdom(struct domain *p, if ( cmd->direction == SCHED_INFO_PUT ) { - unsigned long mcu_adv = params->mcu_adv, - warp = params->warp, - warpl = params->warpl, - warpu = params->warpu; + u32 mcu_adv = params->mcu_adv; + u32 warpback = params->warpback; + s32 warpvalue = params->warpvalue; + s_time_t warpl = params->warpl; + s_time_t warpu = params->warpu; struct bvt_dom_info *inf = BVT_INFO(p); - DPRINTK("Get domain %u bvt mcu_adv=%ld, warp=%ld, " + DPRINTK("Get domain %u bvt mcu_adv=%u, warpback=%d, warpvalue=%d" "warpl=%ld, warpu=%ld\n", - p->domain, inf->mcu_advance, inf->warp, + p->domain, inf->mcu_advance, inf->warpback, inf->warpvalue, inf->warpl, inf->warpu ); /* Sanity -- this can avoid divide-by-zero. */ @@ -321,13 +371,15 @@ int bvt_adjdom(struct domain *p, spin_lock_irqsave(&CPU_INFO(p->processor)->run_lock, flags); inf->mcu_advance = mcu_adv; - inf->warp = warp; + inf->warpback = warpback; // TODO - temporary + inf->warp = 1; + inf->warp_value = warpvalue; inf->warpl = warpl; inf->warpu = warpu; - DPRINTK("Set domain %u bvt mcu_adv=%ld, warp=%ld, " + DPRINTK("Get domain %u bvt mcu_adv=%u, warpback=%d, warpvalue=%d" "warpl=%ld, warpu=%ld\n", - p->domain, inf->mcu_advance, inf->warp, + p->domain, inf->mcu_advance, inf->warpback, inf->warpvalue, inf->warpl, inf->warpu ); spin_unlock_irqrestore(&CPU_INFO(p->processor)->run_lock, flags); @@ -337,10 +389,11 @@ int bvt_adjdom(struct domain *p, struct bvt_dom_info *inf = BVT_INFO(p); spin_lock_irqsave(&CPU_INFO(p->processor)->run_lock, flags); - params->mcu_adv = inf->mcu_advance; - params->warp = inf->warp; - params->warpl = inf->warpl; - params->warpu = inf->warpu; + params->mcu_adv = inf->mcu_advance; + params->warpvalue = inf->warp_value; + params->warpback = inf->warpback; + params->warpl = inf->warpl; + params->warpu = inf->warpu; spin_unlock_irqrestore(&CPU_INFO(p->processor)->run_lock, flags); } @@ -380,7 +433,8 @@ static task_slice_t bvt_do_schedule(s_time_t now) { prev_inf->avt = calc_avt(prev, now); prev_inf->evt = calc_evt(prev, prev_inf->avt); - + + rem_ac_timer(&prev_inf->warp_timer); __del_from_runqueue(prev); if ( domain_runnable(prev) ) @@ -489,6 +543,13 @@ static task_slice_t bvt_do_schedule(s_time_t now) ASSERT(r_time >= ctx_allow); sched_done: + if(next_inf->warp && next_inf->warpl > 0) // TODO - already added? + { + /* Set the timer up */ + next_inf->warp_timer.expires = now + next_inf->warpl; + /* Add it to the heap */ + add_ac_timer(&next_inf->warp_timer); + } ret.task = next; ret.time = r_time; return ret; @@ -499,7 +560,7 @@ static void bvt_dump_runq_el(struct domain *p) { struct bvt_dom_info *inf = BVT_INFO(p); - printk("mcua=0x%04lX ev=0x%08X av=0x%08X ", + printk("mcua=%d ev=0x%08X av=0x%08X ", inf->mcu_advance, inf->evt, inf->avt); } @@ -540,8 +601,8 @@ static void bvt_dump_cpu_state(int i) /* We use cache to create the bvt_dom_infos this functions makes sure that the run_list - is initialised properly. The new domain needs - NOT to appear as to be on the runqueue */ + is initialised properly. + Call to __task_on_runqueue needs to return false */ static void cache_constructor(void *arg1, xmem_cache_t *arg2, unsigned long arg3) { struct bvt_dom_info *dom_inf = (struct bvt_dom_info*)arg1; diff --git a/xen/include/hypervisor-ifs/sched_ctl.h b/xen/include/hypervisor-ifs/sched_ctl.h index 17daa7aaea..0a07cc8c95 100644 --- a/xen/include/hypervisor-ifs/sched_ctl.h +++ b/xen/include/hypervisor-ifs/sched_ctl.h @@ -56,10 +56,11 @@ struct sched_adjdom_cmd union { /* 16 */ struct bvt_adjdom { - u32 mcu_adv; /* 16: mcu advance: inverse of weight */ - u32 warp; /* 20: time warp */ - u32 warpl; /* 24: warp limit */ - u32 warpu; /* 28: unwarp time requirement */ + u32 mcu_adv; /* 16: mcu advance: inverse of weight */ + u32 warpback; /* 20: warp? */ + s32 warpvalue; /* 24: warp value */ + long long warpl; /* 32: warp limit */ + long long warpu; /* 40: unwarp time requirement */ } PACKED bvt; struct fbvt_adjdom -- 2.30.2